/**
 * Copyright (C) 2010, 2011 Neofonie GmbH
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the Apache License, Version 2.0
 * (the "License"); you may not use this file except in compliance with
 * the License.  You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package eu.dicodeproject.blogimport.filereader;

import java.io.File;
import java.util.concurrent.BlockingQueue;
import java.util.concurrent.LinkedBlockingQueue;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.sadun.util.polling.CycleEndEvent;
import org.sadun.util.polling.CycleStartEvent;
import org.sadun.util.polling.DirectoryLookupEndEvent;
import org.sadun.util.polling.DirectoryLookupStartEvent;
import org.sadun.util.polling.FileFoundEvent;
import org.sadun.util.polling.FileMovedEvent;
import org.sadun.util.polling.FileSetFoundEvent;
import org.sadun.util.polling.PollManager;

/**
 * Event handler for our polling reader. The PollManager handles all events
 * produced by the DirectoryPoller which monitors a set of directories for
 * incoming files.
 * 
 * 
 * 
 */
public class BlogImporterPollManager implements PollManager {

  private static final Logger LOG = LoggerFactory.getLogger(BlogImporterPollManager.class);

  private PollingMutex monitor;

  private int queueSize = 500;

  private static int fileSetCounter = 0;

  /** Queue for the files found in the polling directory */
  private BlockingQueue<File> fileQueue = new LinkedBlockingQueue<File>(this.queueSize);

  /**
   * File queue containing all documents found in the polling directory
   * 
   * @return the file queue
   */
  public BlockingQueue<File> getFileQueue() {
    return fileQueue;
  }

  /**
   * 
   * @see org.sadun.util.polling.PollManager#cycleEnded(org.sadun.util.polling.CycleEndEvent)
   */
  @Override
  public void cycleEnded(CycleEndEvent event) {
    LOG.debug("ended cyle");
  }

  /**
   * 
   * @see org.sadun.util.polling.PollManager#cycleStarted(org.sadun.util.polling.CycleStartEvent)
   */
  @Override
  public void cycleStarted(CycleStartEvent event) {
    LOG.debug("starting cyle");
  }

  /**
   * 
   * @see org.sadun.util.polling.PollManager#directoryLookupEnded(org.sadun.util.polling.DirectoryLookupEndEvent)
   */
  @Override
  public void directoryLookupEnded(DirectoryLookupEndEvent event) {
    LOG.debug("ended directory lookup");
  }

  /**
   * 
   * @see org.sadun.util.polling.PollManager#directoryLookupStarted(org.sadun.util.polling.DirectoryLookupStartEvent)
   */
  @Override
  public void directoryLookupStarted(DirectoryLookupStartEvent event) {
    LOG.debug("started directory lookup");
  }

  /**
   * 
   * @see org.sadun.util.polling.PollManager#exceptionDeletingTargetFile(java.io.File)
   */
  @Override
  public void exceptionDeletingTargetFile(File file) {
    LOG.warn("Exception while deleting file:" + file.getPath());
  }

  /**
   * 
   * @see org.sadun.util.polling.PollManager#exceptionMovingFile(java.io.File,
   *      java.io.File)
   */
  @Override
  public void exceptionMovingFile(File event, File file) {
    LOG.warn("Exception while moving file:" + file.getPath());
  }

  /**
   * 
   * @see org.sadun.util.polling.PollManager#fileFound(org.sadun.util.polling.FileFoundEvent)
   */
  @Override
  public void fileFound(FileFoundEvent event) {
    LOG.debug("fileFound " + event.getFile().getName());
  }

  /**
   * 
   * @see org.sadun.util.polling.PollManager#fileMoved(org.sadun.util.polling.FileMovedEvent)
   */

  @Override
  public void fileMoved(FileMovedEvent event) {
    LOG.debug("fileMoved from " + event.getOriginalPath() + " to " + event.getPath());
  }

  /**
   * If we are notified of a FileSetFoundEvent, all files are added to the
   * queue.
   * 
   * @see org.sadun.util.polling.PollManager#fileSetFound(org.sadun.util.polling.FileSetFoundEvent)
   */
  @Override
  public void fileSetFound(FileSetFoundEvent event) {
    
    fileSetCounter++;
    
    synchronized (this.monitor) {
      this.monitor.setLock(false);
    }

    LOG.debug("Files set " + fileSetCounter + "found");
    File[] files = event.getFiles();

    for (int i = 0; i < files.length; i++) {
      try {
        // may block if queue has no more capacity
        LOG.debug(fileSetCounter + " File set: fileFound " + files[i].getPath());
        this.fileQueue.put(new File(files[i].getPath()));
      } catch (InterruptedException e) {
        LOG.error("Interrupted while writing to queue", e);
      }
    }

  }

  /**
   * Monitor for synchronization with file consumer.
   * 
   * @param monitor
   *          the monitor to set
   */
  public void setMonitor(final PollingMutex monitor) {
    this.monitor = monitor;
  }
}
